package com.aube.interact.fighter.card;

import android.animation.Animator;
import android.animation.AnimatorListenerAdapter;
import android.animation.AnimatorSet;
import android.animation.ObjectAnimator;
import android.animation.ValueAnimator;
import android.content.Context;
import android.graphics.Bitmap;
import android.graphics.Color;
import android.graphics.Paint;
import android.text.Spannable;
import android.text.SpannableStringBuilder;
import android.util.AttributeSet;
import android.view.View;
import android.view.ViewGroup;
import android.view.animation.Animation;
import android.view.animation.AnimationUtils;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.RelativeLayout;
import android.widget.TextView;

import com.android.volley.Response;
import com.android.volley.VolleyError;
import com.aube.interact.fighter.R;
import com.aube.interact.fighter.ViewGenerator;
import com.aube.interact.fighter.control.CardsController;
import com.aube.interact.fighter.control.DataManager;
import com.aube.interact.fighter.model.GameConfig;
import com.aube.interact.fighter.model.OptionItem;
import com.aube.interact.fighter.model.ReportResultModel;
import com.aube.interact.fighter.model.TimeLinePiece;
import com.huyn.baseframework.ImageLoader;
import com.huyn.baseframework.dynamicload.video.model.GoodsItem;
import com.huyn.baseframework.model.ChannelDetail;
import com.huyn.baseframework.net.BFJSONRequest;
import com.huyn.baseframework.net.HttpRequestLoader;
import com.huyn.baseframework.net.OpenApi;
import com.huyn.baseframework.statistics.AubeStatisticEvents;
import com.huyn.baseframework.statistics.AubeStatisticTool;
import com.huyn.baseframework.statistics.EventValuePair;
import com.huyn.baseframework.utils.StringUtils;
import com.huyn.baseframework.utils.SysUtil;

import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;

/**
 * Created by hill on 10/24.
 */
public abstract class BaseCardNew extends LinearLayout implements CardsController.IDataSyncHelper {

    protected static final String TYPE_INFO = "INFO";
    protected static final String TYPE_QA = "QA";
    protected static final String TYPE_VOTE = "VOTE";
    protected static final String TYPE_PK = "PK";
    protected static final String TYPE_GUESS = "GUESS";

    protected Context mContext;

    protected IDataSyncSender iSender;

    protected TimeLinePiece mData;
    protected ChannelDetail mChannelDetail;

    protected float indexX=-1, indexY=-1;

    protected int mContentHeight = 0;
    protected int mMinHeight = 0;

    protected int mScreenWidth, mScreenHeight;

    protected TextView mTitle, mDesp, mFoldStateTxt;
    protected ImageView mCollapse, mClose;
    protected View mDespLayout;

    public BaseCardNew(Context context) {
        this(context, null);
    }
    public BaseCardNew(Context context, AttributeSet attrs) {
        this(context, attrs, 0);
    }
    public BaseCardNew(Context context, AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);

        this.mContext = context;

        setOnClickListener(new OnClickListener() {
            @Override
            public void onClick(View v) {
                //do nothing
            }
        });

        mScreenWidth = SysUtil.getAbsoluteScreenWidth(context);
        mScreenHeight = SysUtil.getAbsoluteScreenHeight(context);
    }

    public void init(TimeLinePiece data, ChannelDetail channelDetail) {
        this.mData = data;
        this.mChannelDetail = channelDetail;
    }

    public abstract String getType();

    protected int measure(int measureSpec){
        int mode = MeasureSpec.getMode(measureSpec);
        int size = MeasureSpec.getSize(measureSpec);
        if(mode == MeasureSpec.EXACTLY){
            return size;
        }
        return -1;
    }

    private float getTextHeight() {
        Paint paint = mTitle.getPaint();
        return Math.abs(paint.ascent());
    }

    protected void fillTextWidthDrawable(final TextView textView, String url, final String text) {
        ImageLoader.getInstance(getContext()).preloadBitmap(url, new ImageLoader.IPreloadCallback<Bitmap>() {
            @Override
            public void onSuccess(Bitmap bitmap) {
                if (bitmap == null)
                    return;

                SpannableStringBuilder builder = new SpannableStringBuilder("[star]  " + text);
                builder.setSpan(new ExtendImageSpan(getContext(), bitmap, getTextHeight()), 0, 6, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
                textView.setText(builder);
            }

            @Override
            public void onFail() {

            }
        });
    }

    /**
     * TODO 需要考虑到卡片是否超出屏幕
     */
    public void updatePosition() {
        if(mData != null) {
            float[] indexes = mData.getCardIndex();
            indexX = indexes[0];
            indexY = indexes[1];

            if(indexX >=0)
                setTranslationX(mScreenWidth*indexX);
            if(indexY >=0)
                setTranslationY(mScreenHeight*indexY);
        }
    }

    protected int mInAnim = R.anim.fade_in;
    protected int mOutAnim = R.anim.fade_out;
    protected void generateAnim() {
        String animation = mData.getAnimEffects();
        if(StringUtils.isNotBlank(animation)) {
            try {
                int animStyle = Integer.parseInt(animation);
                switch (animStyle) {
                    case 1:
                        mInAnim = R.anim.push_top_in;
                        mOutAnim = R.anim.push_top_out;
                        return;
                    case 2:
                        mInAnim = R.anim.push_bottom_in;
                        mOutAnim = R.anim.push_bottom_out;
                        return;
                    case 3:
                        mInAnim = R.anim.push_left_in;
                        mOutAnim = R.anim.push_left_out;
                        return;
                    case 4:
                        mInAnim = R.anim.push_right_in;
                        mOutAnim = R.anim.push_right_out;
                        return;
                    case 5:
                        mInAnim = R.anim.push_left_top_in;
                        mOutAnim = R.anim.push_left_top_out;
                        return;
                    case 6:
                        mInAnim = R.anim.push_right_top_in;
                        mOutAnim = R.anim.push_right_top_out;
                        return;
                    case 7:
                        mInAnim = R.anim.push_left_bottom_in;
                        mOutAnim = R.anim.push_left_bottom_out;
                        return;
                    case 8:
                        mInAnim = R.anim.push_right_bottom_in;
                        mOutAnim = R.anim.push_right_bottom_out;
                        return;
                }
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
    }

    public void animIn(RelativeLayout parent, Animation.AnimationListener listener) {
        int relativePisition = mData.getRelativePosition();
        RelativeLayout.LayoutParams params = new RelativeLayout.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT);
        if(relativePisition >= 0) {
            ViewGenerator.generateParamsStyle(params, relativePisition);
        } else {
            //absolute position
            updatePosition();
        }
        parent.addView(this, params);

        generateAnim();

        Animation anim = AnimationUtils.loadAnimation(getContext(), mInAnim);
        anim.setAnimationListener(listener);
        startAnimation(anim);
    }

    public void animOut(Animation.AnimationListener listener) {
        Animation anim = AnimationUtils.loadAnimation(getContext(), mOutAnim);
        anim.setAnimationListener(listener);
        startAnimation(anim);
    }

    public void updateCountDown(String time) {

    }

    public void setupSender(IDataSyncSender iSender) {
        this.iSender = iSender;
        doNext();
    }

    public void doNext() {}

    public interface IDataSyncSender {
        public void startSync(String id, boolean oneTime);
        public void postResult(String id, List<OptionItem> results, String cancelId, String selectedId);
        public void close();
        public void onAddRewardGoods(List<GoodsItem> data);
        public void showInfoCard(TimeLinePiece data);
        public void addFragment(String id);
        public GameConfig getConfig();
    }

    public void close() {
        if(iSender != null)
            iSender.close();
    }

    public void removeSender() {
        iSender = null;
    }

    public void clearData() {

    }

    public void report(String rid, String msg, List<GoodsItem> goodsItemList) {

    }

    public void report(final String rid, final String optionId, final String cancelId, final boolean reportResult) {
        clearData();
        HashMap<String, String> parameterMap = new HashMap<String, String>();
        parameterMap.put("rid", rid);
        if(StringUtils.isNotBlank(cancelId))
            parameterMap.put("cancelOpId", cancelId);
        if(StringUtils.isNotBlank(optionId) && !optionId.equalsIgnoreCase(cancelId))
            parameterMap.put("optionId", optionId);
        parameterMap.put("type", getType());

        //保存
        DataManager.getInstance(getContext()).updateSelectedOptionId(rid, optionId);

        parameterMap.put(OpenApi.API_METHOD, OpenApi.REPORT_DATA);
        BFJSONRequest request = new BFJSONRequest(ReportResultModel.class, parameterMap, new Response.Listener<ReportResultModel>() {

            @Override
            public void onResponse(ReportResultModel response) {
                if(response != null && response.success()) {
                    report(optionId, response.getMessage(), response.getGoodsList());

                    if (reportResult && iSender != null) {
                        iSender.postResult(rid, response.getOptions(), cancelId, optionId);
                    }
                }
            }

            @Override
            public void onErrorResponse(VolleyError error) {
            }

            @Override
            public void onStart() {
            }
        });
        HttpRequestLoader.getInstance(getContext()).startCacheLoader("", request, true);
    }

    public String appendPercentStr(int value) {
//        return "<font><small>&nbsp;" + value + "%</small></font>";
        return value+"%";
    }


    protected void swithWindow(boolean toCollapse, View mGroup) {
        switchFoldState(!toCollapse);
        animGroup(!toCollapse, mGroup);
    }

    protected void switchFoldState(boolean isExpanded) {
        if(!isExpanded) {
            mCollapse.setImageResource(R.drawable.card_expand);
            mFoldStateTxt.setText("展开");
        } else {
            mCollapse.setImageResource(R.drawable.card_fold);
            mFoldStateTxt.setText("收起");

            //统计展开卡片事件
            AubeStatisticTool.getInstance(getContext()).report(AubeStatisticEvents.INTERACT_EXPAND,
                    AubeStatisticEvents.formatValues(new EventValuePair("vid", ""), new EventValuePair("rid", mData.getRid()), new EventValuePair("type", mData.type)));
        }
    }

    protected void reportOptionSelectEvent(EventValuePair data) {
        AubeStatisticTool.getInstance(getContext()).report(AubeStatisticEvents.INTERACT_OPTION_SELECT,
                AubeStatisticEvents.formatValues(new EventValuePair("vid", ""), new EventValuePair("rid", mData.getRid()), new EventValuePair("type", mData.type), data));
    }

    protected void reportOptionSelectEvent(String key, String value) {
        reportOptionSelectEvent(new EventValuePair(key, value));
    }

    private static final int DURATION = 200;
    protected void animGroup(final boolean expand, final View mGroup) {
        float startValue = expand ? mMinHeight : mContentHeight;
        float endValue = expand ? mContentHeight : mMinHeight;
        final ValueAnimator anim = ValueAnimator.ofFloat(startValue, endValue);
        anim.setDuration(DURATION);
        anim.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
            @Override
            public void onAnimationUpdate(ValueAnimator animation) {
                float value = (float) animation.getAnimatedValue();

                LayoutParams params = (LayoutParams) mGroup.getLayoutParams();
                params.height = (int) value;
                mGroup.setLayoutParams(params);
            }
        });
        anim.addListener(new AnimatorListenerAdapter() {
            @Override
            public void onAnimationStart(Animator animation) {
                if (expand) {
                    mGroup.setAlpha(0);
                    mGroup.setVisibility(View.VISIBLE);

                    hideDivider();
                }
            }

            @Override
            public void onAnimationEnd(Animator animation) {
                if (!expand) {
                    mGroup.setVisibility(View.GONE);

                    showDivider();
                }
            }
        });

        AnimatorSet set = new AnimatorSet();
        Animator alphaAnim = ObjectAnimator.ofFloat(mGroup, "alpha", expand ? 0 : 1, expand ? 1 : 0);
        alphaAnim.setDuration(DURATION);

        if(expand) {
            set.playSequentially(anim, alphaAnim);
        } else {
            set.playSequentially(alphaAnim, anim);
        }
        set.start();
    }

    protected void hideDivider(){}
    protected void showDivider(){}

    public void reSortData(HashMap<String, Float> mSet) {
        String maxId="";
        float max = 0;
        float total = 0;
        Iterator<Map.Entry<String, Float>> iterator = mSet.entrySet().iterator();
        while (iterator.hasNext()) {
            Map.Entry<String, Float> entry = iterator.next();
            total += entry.getValue();
            if(entry.getValue() > max) {
                max = entry.getValue();
                maxId = entry.getKey();
            }
        }

        if(total > 100) {
            float value = mSet.get(maxId);
            mSet.put(maxId, value + 100 - total);
        }
    }

}
